using System;
using System.Collections.Generic;
using System.Text;
using Barrage.Global;
using Barrage.Global.Vertex;
using Barrage.Shaders;
using SlimDX.Direct3D9;
using SlimDX;

namespace Barrage
{
    /// <summary>
    /// Base clas for renderable meshes
    /// </summary>
    public abstract class Mesh:IDisposable
    {
        /// <summary>
        /// List of materials associated to the mesh (each material will be rendered once)
        /// </summary>
        public List<Material> Materials { get { return materials; } }
        /// <summary>
        /// List of materials associated to the mesh (each material will be rendered once)
        /// </summary>
        protected List<Material> materials = new List<Material>(1);

        /// <summary>
        /// First material in the material list
        /// </summary>
        public Material FirstMaterial { get { return materials[0]; } }

        /// <summary>
        /// Shader that will be used to render the mesh. Null to use the default shader
        /// </summary>
        protected Shader shader;
        /// <summary>
        /// Shader that will be used to render the mesh. Null to use the default shader
        /// </summary>
        public Shader Shader { get { return shader; } set { shader = value; } }
        
        /// <summary>
        /// Renders the mesh
        /// </summary>
        /// <param name="item">Item that will be rendered</param>
        public abstract void Render(Barrage.Item item);

        /// <summary>
        /// Creates a mesh with the specified shader
        /// </summary>
        /// <param name="shader">Shader used to render the mesh</param>
        public Mesh(Shader shader)
        {
            this.shader = shader;
        }

        /// <summary>
        /// Clears every material in the material list
        /// </summary>
        public void ClearMaterials()
        {
            materials.Clear();
        }

        /// <summary>
        /// Creates a mesh with the default shader
        /// </summary>
        public Mesh()
        {
            this.shader = BaseShader.Instance;
        }

        /// <summary>
        /// Free resources
        /// </summary>
        public virtual void Dispose()
        {
            shader = null;
            materials.Clear();
            materials = null;
            NLog.LogManager.GetLogger(ToString()).Debug("Disposing");
            GC.SuppressFinalize(this);
        }

        /// <summary>
        /// Destructor. Free resources
        /// </summary>
        ~Mesh()
        {
            Dispose();
        }
    }
}
